#define SIZE_MAX_MATRIX			128
#define SIZE_CHARLIST			SIZE_MAX_MATRIX*SIZE_MAX_MATRIX*4+1

#include <stdio.h>
#include <string.h>

int mat1[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX];
int mat2[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX];
int prod[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX];
int row = 0;
int column = 0;


/** ============================================================================
 * @func printMatrix
 *
 * @desc This function prints a matrix
 * =============================================================================
*/
void printMatrix(int matrix[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int size){
    int i,j;
    
    for(i=0;i<size;i++){
        for(j=0;j<size;j++){
            printf("%d ",matrix[i][j]);
        }
        printf("\n");
    }
    printf("\n==============================\n");
    
}


/** ============================================================================
 * @func matMult
 * 
 * @desc This function multiplies two matrices
 *
 * @param mat1 matrix A
 * @param mat2 matrix B
 * @param prod A*B matrix
 * @param size dimension of matrices
 * ============================================================================
*/
void matMult(int mat1[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int mat2[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int prod[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int size){
    int i, j, k;
    for (i = 0;i < size; i++)
    {
        for (j = 0; j < size; j++)
        {
            prod[i][j]=0;
            for(k=0;k<size;k++)
                prod[i][j] = prod[i][j]+mat1[i][k] * mat2[k][j];
        }
    }
}

/** ============================================================================
 * @func Create_Matrix
 *
 * @desc This function creates two matrices of the size MatrixSize
 *
 *  @param MatrixSize dimension of matrix
 * =============================================================================
*/
void Create_Matrix(int MatrixSize){
    int i=0, j=0;
    printf ("========== create a matrix of (%d x %d)  ==========\n", MatrixSize,MatrixSize);

	
	
    for (i = 0;i < MatrixSize; i++)
    {
        for (j = 0; j < MatrixSize; j++)
        {
            mat1[i][j] = i+j*2;
        }
    }
    
    printf("Matrix A\n\n");
    printMatrix(mat1, MatrixSize);
    
    for (i = 0;i < MatrixSize; i++)
    {
        for (j = 0; j < MatrixSize; j++)
        {
            mat2[i][j] = i+j*3;
        }
    }
    
    printf("Matrix B\n\n");
    printMatrix(mat2, MatrixSize);
}


/** ============================================================================
 * @func Verify
 *
 * @desc This function verifies two matrices against each other
 *
 *  @param mat1 Matrix A
 *  @param mat2 Matrix B
 *  @param size Dimension of matrices
 *  @param *row row index
 *  @param *column column index
 * =============================================================================
*/
void Verify(int mat1[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int mat2[SIZE_MAX_MATRIX][SIZE_MAX_MATRIX], int size, int *row, int *column)
{
    int i, j;
    for (i = 0;i < size; i++)
    {
        for (j = 0; j < size; j++)
        {
           if (mat1[i][j] != mat2[i][j]) 
           {
                *row = i;
                *column = j;
				printf("Entry (%d, %d) is FAULT!!!\n", i, j);
                break;
           }
           printf("Entry (%d, %d) is OK!!!\n", i, j);
        }
    }
}


/** ============================================================================
 * @func main
 *
 * @desc entry point of the application
 * =============================================================================
*/
int main(void){
    Create_Matrix(SIZE_MAX_MATRIX);
    matMult(mat1, mat2, prod, SIZE_MAX_MATRIX);
	
	printf("Matrix A*B\n");
	printMatrix(prod, SIZE_MAX_MATRIX);
	
    Verify(mat1, mat2, SIZE_MAX_MATRIX, &row, &column);
}